/**
 * 
 */
package com.roc.web.action.finance;

import java.io.BufferedReader;
import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.UnsupportedEncodingException;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.Date;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.TreeMap;

import org.apache.commons.lang3.StringUtils;
import org.apache.log4j.LogManager;
import org.apache.log4j.Logger;
import org.apache.poi.hssf.usermodel.HSSFWorkbook;
import org.apache.struts2.convention.annotation.Action;
import org.apache.struts2.convention.annotation.InterceptorRef;
import org.apache.struts2.convention.annotation.Namespace;
import org.apache.struts2.convention.annotation.Result;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.config.BeanDefinition;
import org.springframework.context.annotation.Scope;
import org.springframework.stereotype.Controller;
import com.opensymphony.xwork2.ActionContext;
import com.roc.page.BaseSearchCondition;
import com.roc.page.PaginationBaseAction;
import com.roc.pojo.CalcuBean;
import com.roc.pojo.DuizhangBean;
import com.roc.pojo.Operators;
import com.roc.service.IExcelService;
import com.roc.service.IPagenitionService;
import com.roc.service.ServiceException;
import com.roc.service.setting.ISettflagService;
import com.roc.util.Constance;
import com.roc.util.constant.Constant;
import com.roc.util.constant.DuiZhangType;
import com.roc.util.constant.TerminalBrand;
import com.roc.web.action.OperatorQuerySearchCondition;

/**
 * @author Feng haitao
 * 
 */
@Controller
@Scope(BeanDefinition.SCOPE_PROTOTYPE)
@Namespace("/fina")
public class TermFileAction extends PaginationBaseAction {

	static Logger logger = LogManager.getLogger(TermFileAction.class);

	private File upload;

	private String uploadContentType;
	private String uploadFileName;

	private String chanalCode;
	private String dateFlag;
	private String finaDate;
	private String minDate;
	private String maxDate;
	private InputStream excelFile;
	private String  excelName;

	private FinanceSearchCondition searchCondition;
	@Autowired
	ISettflagService settflagService;
	@Autowired
	IPagenitionService pagenitionService;
	@Autowired
	IExcelService excelService;
	

	@Action(value = "finaInit", results = { @Result(name = "success", location = "/pages/fianance/financeFileUpload.jsp") })
	public String init() throws Exception {
		Operators loginOpers = (Operators) ActionContext.getContext()
				.getSession().get(Constant.SESSION_LOGIN_MERCHANT);

		return SUCCESS;
	}
	
	
	@Action(value = "upload", interceptorRefs = {
			@InterceptorRef(value = "token"),
			@InterceptorRef(value = "rocDefaultStack", params = {
					"fileUpload.allowedExtensions", "txt",
					"fileUpload.maximumSize", "100000000" }) }, results = {
			@Result(location = "/message.jsp"),
			
			@Result(name = "success", location = "/pages/fianance/financeFileUpload.jsp"),
			@Result(name = "error", location = "/error.jsp"),
			@Result(name = "invalid.token", location = "/error.jsp") })
	public String upload() throws Exception {
		Operators loginOpers = (Operators) ActionContext.getContext()
				.getSession().get(Constant.SESSION_LOGIN_MERCHANT);
		 Map<String,DuizhangBean> map= new  HashMap<String,DuizhangBean>();
		 Map<String,DuizhangBean> map2= new  HashMap<String,DuizhangBean>();
		 Map<String,DuizhangBean> map1= new  HashMap<String,DuizhangBean>();
		if (upload == null) {
			addActionError("请选择文件");
			return ERROR;
		}
		if(StringUtils.isNotBlank(finaDate)){
			finaDate = finaDate.replace("-", "");
		}
		if(StringUtils.isNotBlank(minDate)){
			minDate = minDate.replace("-", "");
		}
		if(StringUtils.isNotBlank(maxDate)){
			maxDate = maxDate.replace("-", "");
		}
		//解析对账文件获取map
		map = process(upload);
		if(map.size()==0){
			addActionMessage("对账文件不合法！");
		}else{
			//验证工作日对账日期是否合法。
//			if(StringUtils.isNotBlank(finaDate)){
//				String nextday = getNextDay(finaDate);
//				Iterator iter = map.entrySet().iterator();
//				while (iter.hasNext()) {
//					Map.Entry entry = (Map.Entry) iter.next();
//					String key = (String) entry.getKey();
//					DuizhangBean val = (DuizhangBean) entry.getValue();
//					if(Long.valueOf(nextday+"222000")>Long.valueOf(val.getReqdate()+val.getReqtime())||Long.valueOf(finaDate+"224000")<Long.valueOf(val.getReqdate()+val.getReqtime())){
//						addActionMessage("对账文件内日期和选择对账日期不符合！");	
//						return SUCCESS;
//					}
//				}
//			}
			//验证节假日对账文件是否合法
//			if(StringUtils.isNotBlank(minDate)&&StringUtils.isNotBlank(maxDate)){
//				String minnextday = getNextDay(minDate);
//				Iterator iter = map.entrySet().iterator();
//				while (iter.hasNext()) {
//					Map.Entry entry = (Map.Entry) iter.next();
//					String key = (String) entry.getKey();
//					DuizhangBean val = (DuizhangBean) entry.getValue();
//					if(Long.valueOf(minnextday+"222000")>Long.valueOf(val.getReqdate()+val.getReqtime())||Long.valueOf(maxDate+"224000")<Long.valueOf(val.getReqdate()+val.getReqtime())){
//						addActionMessage("对账文件内日期和选择对账日期不符合！");	
//						return SUCCESS;
//					}
//				}
//			}
			
			int i =map.size();
			//获取本地交易数据
			map1=settflagService.queryDuizhangBean(minDate, maxDate, finaDate, dateFlag);
			int j =map1.size();
			Iterator iter = map.entrySet().iterator();
			while (iter.hasNext()) {
				Map.Entry entry = (Map.Entry) iter.next();
				String key = (String) entry.getKey();
				DuizhangBean val = (DuizhangBean) entry.getValue();
				if(map1.containsKey(key)){	
					map2.put(key, val);
					map1.remove(key);
				}else{
					//根据对账文件的数据，根据流水号+金额，查询本地数据（剔除日切包含的数据）
					int k = settflagService.queryTrancount(val);
					if(k>0){
					 map2.put(key, val);	
					 map.remove(val);
					 settflagService.deleteDZ(val);
					}
					/**
					 * 
					 
					else{
					//不包含的话，查询查错账表，
						int l = settflagService.queryDZcount(val);
						if(l>0){
							settflagService.deleteDZ(val);
						}
					}*/
				}
			}
			
			Iterator it = map2.keySet().iterator();
			while(it.hasNext()){	
				String key = (String) it.next();  
				if(map.containsKey(key)){	
					map.remove(key);
				}
			}
			
			System.out.println("对账平的记录"+map2.size());
			boolean b =settflagService.insertCHZ(map, map1,map2);
			if(b){
				int a = i-map.size();
				String str="通道交易数据总计【"+i+"】条；通道交易数据对账平【"+a+"】条；通道交易数据对账不平【"+map.size()+"】条；";
				if(j>0){
					int aa = j-map1.size();
					str=str+"本地交易数据总计【"+j+"】条记录；本地交易数据对账平【"+aa+"】条；本地交易数据对账不平【"+map1.size()+"】条。";
				}
				addActionMessage(str);
			}else{
				addActionMessage("对账失败");
			}
		}
		
		return SUCCESS;
	}
	//获取一个日期的前一天
	public  String getNextDay(String dat) {	
		 SimpleDateFormat formatDate = new SimpleDateFormat("yyyyMMdd");     
		// String dat = formatDate.format(dat);
		Date date =new Date();
		String s = "";
		try {
			date = formatDate.parse(dat);
			Calendar calendar = Calendar.getInstance();		
			calendar.setTime(date);	
			calendar.add(Calendar.DAY_OF_MONTH, -1);	
			date = calendar.getTime();		
		    s=formatDate.format(date);
		} catch (ParseException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		return s;
	}
	
	// 解析txt文件。
	public Map<String,DuizhangBean> checkfile(File file) throws Exception {
		
		Map<String,DuizhangBean> map = new HashMap<String,DuizhangBean>();
		try {
			String encoding = "GBK";
			if (file.isFile() && file.exists()) { // 判断文件是否存在
				InputStreamReader read = new InputStreamReader(new FileInputStream(file), encoding);// 考虑到编码格式
				BufferedReader bufferedReader = new BufferedReader(read);
				String lineTxt = null;
				while ((lineTxt =bufferedReader.readLine())!= null) {
				  String[] str=	lineTxt.split("\\|");
				  if(str.length>5){
				  
					  DuizhangBean dz= new DuizhangBean();
					  dz.setAccbranchid(str[0]);
					  dz.setAccbranchname(str[1]);
					  dz.setServcode(str[2].trim());
					  dz.setReqdate(str[3]);
					  dz.setReqtime(str[4]);
					  dz.setReqlogno(str[5]);
					  dz.setHostmerchid(str[6]);
					  dz.setHosttermid(str[7]);
					  
					  dz.setLocaldate(str[8]);
					  dz.setLocaltime(str[9]);
					  dz.setLocallogno(str[10]);
					  dz.setAccount(str[11]);
					  dz.setTraamt(str[12]);
					  
					  dz.setDiffflag("1");
					  dz.setProcessflag("1");
					  String time="";
					  Date dt = new Date();  
				      SimpleDateFormat sdf = new SimpleDateFormat("yyyyMMddHHmmss");  
				      time=sdf.format(dt); 
					  dz.setInsertt(time);
//					  CalcuBean calcuBean = new CalcuBean();
//					  calcuBean=  settflagService.queryCalcuBean(str[3], str[4], str[5]);
//					  if(calcuBean!=null){
//						  dz.setHostmerchid(calcuBean.getMerno());
//						  dz.setHosttermid(calcuBean.getTermid()); 
//					  }
					  map.put(dz.getReqlogno()+dz.getReqdate()+dz.getReqtime()+dz.getHostmerchid()+dz.getHosttermid(), dz);
				  }
				}
				read.close();
			} else {
				System.out.println("找不到指定的文件");
			}
		} catch (Exception e) {
			System.out.println("读取文件内容出错");
			e.printStackTrace();
		}
		return map;
	}
	
	// 解析txt文件。
	public Map<String,DuizhangBean> process(File file) throws Exception {
		
		Map<String,DuizhangBean> map = new HashMap<String,DuizhangBean>();
		try {
			String encoding = "GBK";
			if (file.isFile() && file.exists()) { // 判断文件是否存在
				InputStreamReader read = new InputStreamReader(new FileInputStream(file), encoding);// 考虑到编码格式
				BufferedReader bufferedReader = new BufferedReader(read);
				String lineTxt = null;
				while ((lineTxt =bufferedReader.readLine())!= null) {
				  String[] str=	lineTxt.split("\\|");
				  if(str.length>5){
				  
					  DuizhangBean dz= new DuizhangBean();
					  dz.setAccbranchid(str[0]);
					  dz.setAccbranchname(str[1]);
					  dz.setServcode(str[2].trim());
					  dz.setReqdate(str[3]);
					  dz.setReqtime(str[4]);
					  dz.setReqlogno(str[5]);
					  dz.setHostmerchid(str[6]);
					  dz.setHosttermid(str[7]);
					  
					  dz.setLocaldate(str[8]);
					  dz.setLocaltime(str[9]);
					  dz.setLocallogno(str[10]);
					  dz.setAccount(str[11]);
					  dz.setTraamt(str[12]);
					  dz.setHostbranthno(str[17]);
					  dz.setHostmerno(str[18]);
					  dz.setHosttermno(str[19]);
					  dz.setDiffflag("1");
					  dz.setProcessflag("1");
					  String time="";
					  Date dt = new Date();  
				      SimpleDateFormat sdf = new SimpleDateFormat("yyyyMMddHHmmss");  
				      time=sdf.format(dt); 
					  dz.setInsertt(time);
//					  CalcuBean calcuBean = new CalcuBean();
//					  calcuBean=  settflagService.queryCalcuBean(str[3], str[4], str[5]);
//					  if(calcuBean!=null){
//						  dz.setHostmerchid(calcuBean.getMerno());
//						  dz.setHosttermid(calcuBean.getTermid()); 
//					  }
					  map.put(dz.getReqlogno()+dz.getReqdate()+dz.getReqtime()+dz.getHostmerchid()+dz.getHosttermid(), dz);
				  }
				}
				read.close();
			} else {
				System.out.println("找不到指定的文件");
			}
		} catch (Exception e) {
			System.out.println("读取文件内容出错");
			e.printStackTrace();
		}
		return map;
	}

	
	@Action(value = "queryInit", results = { @Result(name = "success", location = "/pages/term_file.jsp")
    })
	public String queryInit() {	
		Map<String,String> typeMap=new TreeMap<String, String>();
	
		for (DuiZhangType b : DuiZhangType.values()){  
			typeMap.put(b.getCode(),b.getName());
		}	
		/*typeMap.put("1","通道有本地无");
		typeMap.put("2", "本地有通道无");
		typeMap.put("3","通道有本地撤销");
		typeMap.put("4","通道有本地冲正失败");
		typeMap.put("5","通道有本地冲正");
		*
		*/
		getRequest().setAttribute("typeMap",typeMap);
	   return SUCCESS;
    }
	
	
		
	
	@Action(value = "queryDuiZhang", 
			results = { @Result(name = "success", location = "/pages/term_file.jsp"),
			@Result(name = "error", location = "/error.jsp")
    })
	public String queryDuiZhang(){
		Operators logingOperators = (Operators)getSession().getAttribute(Constant.SESSION_LOGIN_MERCHANT);
		
		
		if(searchCondition==null){
			searchCondition=(FinanceSearchCondition)getSearchConditionFromSession();
			if(searchCondition==null){
				searchCondition=new FinanceSearchCondition();
			}
		}
		try {
			queryInit(); 
			
			int rows=pagenitionService.count(searchCondition);
			if(rows>0){
				searchRsList=pagenitionService.findAll(searchCondition, calcuStart(getCurrentPage()), Constance.PAGE_MAX_SIZE);

			}
			Map<String,String> typeMap=new TreeMap<String, String>();
			
			for (DuiZhangType b : DuiZhangType.values()){  
				typeMap.put(b.getCode(),b.getName());
			}	
			getRequest().setAttribute("typeMap",typeMap);
			this.setTotalPage(this.calcuTotalPage(rows));
			getRequest().setAttribute(SEARCH_RS_LIST, searchRsList);
			getRequest().setAttribute(CURRENT_PAGE, this.getCurrentPage());
			getRequest().setAttribute(TOTAOL_PAGE, this.getTotalPage());
			setSearchToConditionSession(searchCondition);
			
		} catch (ServiceException e) {
			
			logger.error(e.getMessage(),e);
			addActionError(e.getMessage());
			
		}
		
		return SUCCESS;
	}
	
	@Action(value="duiZhangExport",results = {@Result(name="success",type="stream"
			,params = { "contentType", "application/vnd.ms-excel", "inputName",  
			            "excelFile","contentDisposition",  "attachment;filename=${excelName}.xls",
			            "bufferSize", "1024*3" }),@Result(name="error",location="/pages/term_file.jsp") })
	public String duiZhangExport(){

		if(searchCondition==null){
			searchCondition=(FinanceSearchCondition)getSearchConditionFromSession();
			if(searchCondition==null){
				searchCondition=new FinanceSearchCondition();
			}
		}
		try {
			queryInit(); 
			
			int rows=pagenitionService.count(searchCondition);
			if(rows>0){
				searchRsList=pagenitionService.findAll(searchCondition, calcuStart(getCurrentPage()), rows);

			}
			HSSFWorkbook work=excelService.duiZhangQueryExcel(searchRsList,searchCondition.getStartDate(),searchCondition.getEndDate());
			 ByteArrayOutputStream output = new ByteArrayOutputStream();  
			         work.write(output);  
			   
			        byte[] ba = output.toByteArray();  
			         excelFile = new ByteArrayInputStream(ba);  
			         output.flush();  
			         output.close();  
			
			
			
		} catch(Exception e){
			logger.info("######导出Excel失败######");
			addActionError(e.getMessage());
			return ERROR;
	}
		return SUCCESS;
	}
	
	public String getExcelName() {
		String excelName="差错对账详情"+Constance.formateDate();
		 
			try {
				excelName = new String(excelName.getBytes(),"ISO8859-1");
			} catch (UnsupportedEncodingException e) {
				e.printStackTrace();
				logger.info("生成excel名称失败了！");
			}
		 
		return  excelName;
		
	}
	
	
	public InputStream getExcelFile() {
		return excelFile;
	}


	public void setExcelFile(InputStream excelFile) {
		this.excelFile = excelFile;
	}


	public void setExcelName(String excelName) {
		this.excelName = excelName;
	}


	public File getUpload() {
		return upload;
	}

	public void setUpload(File upload) {
		this.upload = upload;
	}

	public String getUploadContentType() {
		return uploadContentType;
	}

	public void setUploadContentType(String uploadContentType) {
		this.uploadContentType = uploadContentType;
	}

	public String getUploadFileName() {
		return uploadFileName;
	}

	public void setUploadFileName(String uploadFileName) {
		this.uploadFileName = uploadFileName;
	}

	@Override
	protected String getInitPageSize() {
		// TODO Auto-generated method stub
		return Constance.PAGE_MAX_SIZE + "";
	}

	@Override
	protected BaseSearchCondition getSearchConditionFromSession() {
		// TODO Auto-generated method stub
		return (FinanceSearchCondition) getSession().getAttribute(
				SEARCH_SESSION_BEAN_FINANCE);
	}

	@Override
	protected BaseSearchCondition getSearchConditionFromSubClass()
			throws Exception {
		// TODO Auto-generated method stub
		return searchCondition;
	}

	@Override
	protected void setSearchConditionToSubClass(
			BaseSearchCondition searchCondition) throws Exception {
		this.setSearchConditionToSubClass(searchCondition);

	}

	@Override
	protected void setSearchToConditionSession(
			BaseSearchCondition searchCondition) {
		getSession().setAttribute(SEARCH_SESSION_BEAN_FINANCE, searchCondition);
	}

	/**
	 * @return the searchCondition
	 */
	public FinanceSearchCondition getSearchCondition() {
		return searchCondition;
	}

	/**
	 * @param searchCondition
	 *            the searchCondition to set
	 */
	public void setSearchCondition(FinanceSearchCondition searchCondition) {
		this.searchCondition = searchCondition;
	}

	public String getChanalCode() {
		return chanalCode;
	}

	public void setChanalCode(String chanalCode) {
		this.chanalCode = chanalCode;
	}

	public String getDateFlag() {
		return dateFlag;
	}

	public void setDateFlag(String dateFlag) {
		this.dateFlag = dateFlag;
	}

	public String getFinaDate() {
		return finaDate;
	}

	public void setFinaDate(String finaDate) {
		this.finaDate = finaDate;
	}

	public String getMinDate() {
		return minDate;
	}

	public void setMinDate(String minDate) {
		this.minDate = minDate;
	}

	public String getMaxDate() {
		return maxDate;
	}

	public void setMaxDate(String maxDate) {
		this.maxDate = maxDate;
	}

}
